package com.example.flightsearch.ui

import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.Spacer
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.lazy.LazyColumn
import androidx.compose.foundation.lazy.items
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.filled.MoreVert
import androidx.compose.material.icons.filled.Search
import androidx.compose.material.icons.outlined.Star
import androidx.compose.material3.Card
import androidx.compose.material3.ExperimentalMaterial3Api
import androidx.compose.material3.Icon
import androidx.compose.material3.MaterialTheme
import androidx.compose.material3.Scaffold
import androidx.compose.material3.SearchBar
import androidx.compose.material3.Text
import androidx.compose.material3.TopAppBar
import androidx.compose.material3.TopAppBarDefaults
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.runtime.saveable.rememberSaveable
import androidx.compose.runtime.setValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.res.dimensionResource
import androidx.compose.ui.res.stringResource
import androidx.compose.ui.text.font.FontWeight
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import androidx.hilt.navigation.compose.hiltViewModel
import com.example.flightsearch.R
import com.example.flightsearch.data.Airport
import kotlinx.coroutines.launch

@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun FlightSearchApp(
    modifier: Modifier = Modifier,
) {
    Scaffold(
        modifier = modifier.padding(top = 24.dp),
        topBar = {
            TopAppBar(
                title = {
                    Text(
                        text = stringResource(id = R.string.app_name),
                        color = MaterialTheme.colorScheme.onPrimary
                    )
                },
                colors = TopAppBarDefaults.topAppBarColors(
                    containerColor = MaterialTheme.colorScheme.primary
                )
            )
        }
    ) { contentPadding ->
        FlightSearchScreen(
            modifier = Modifier.padding(contentPadding)
        )
    }
}

@Composable
fun FlightSearchScreen(
    modifier: Modifier = Modifier,
    viewModel: FlightSearchViewModel = hiltViewModel()
) {
    val uiState = viewModel.uiState
    Column(
        modifier = modifier
            .padding(horizontal = dimensionResource(id = R.dimen.padding_medium))
    ) {
        var query by rememberSaveable { mutableStateOf("") }
        var active by rememberSaveable { mutableStateOf(false) }
        val coroutineScope = rememberCoroutineScope()
        SearchField(
            query = query,
            onQueryChange = {
                query = it
                coroutineScope.launch {
                    viewModel.updateSearchText(it)
                }
            },
            onSearch = {
                active = false
                coroutineScope.launch {
                    viewModel.search(it)
                }
            },
            active = active,
            onActiveChange = {
                active = it
                if (it) {
                    coroutineScope.launch {
                        viewModel.updateSearchText(query)
                    }
                }
            },
            onAirportClick = {
                active = false
                query = it
                coroutineScope.launch {
                    viewModel.search(it)
                }
            },
            airports = uiState.airports,
            modifier = Modifier.fillMaxWidth()
        )

        FlightList(
            flights = uiState.flights,
            toggleFavorite = {
                coroutineScope.launch {
                    viewModel.toggleFavorite(it)
                }
            }
        )
    }
}

@OptIn(ExperimentalMaterial3Api::class)
@Composable
private fun SearchField(
    query: String,
    onQueryChange: (String) -> Unit,
    onSearch: (String) -> Unit,
    active: Boolean,
    onActiveChange: (Boolean) -> Unit,
    onAirportClick: (code: String) -> Unit,
    airports: List<Airport>,
    modifier: Modifier = Modifier
) {
    SearchBar(
        modifier = modifier,
        query = query,
        onQueryChange = onQueryChange,
        onSearch = onSearch,
        active = active,
        onActiveChange = onActiveChange,
        leadingIcon = {
            Icon(
                imageVector = Icons.Default.Search,
                contentDescription = null
            )
        },
        trailingIcon = {
            Icon(
                imageVector = Icons.Filled.MoreVert,
                contentDescription = null
            )
        }
    ) {
        if (active) {
            LazyColumn(
                modifier = Modifier
                    .padding(dimensionResource(id = R.dimen.padding_small)),
            ) {
                items(airports) { airport ->
                    Row(
                        modifier = Modifier
                            .padding(vertical = dimensionResource(id = R.dimen.padding_mini_small))
                            .clickable { onAirportClick(airport.code) }
                    ) {
                        Text(
                            text = airport.code,
                            fontWeight = FontWeight.Bold,
                            modifier = Modifier.padding(end = dimensionResource(id = R.dimen.padding_small))
                        )
                        Text(text = airport.name)
                    }
                }
            }
        }
    }
}

@Composable
private fun FlightList(
    flights: List<Flight>,
    toggleFavorite: (Flight) -> Unit,
    modifier: Modifier = Modifier
) {
    if (flights.isNotEmpty()) {
        Column(
            modifier = modifier
                .fillMaxWidth()
                .padding(vertical = dimensionResource(id = R.dimen.padding_medium))
        ) {
            Text(
                text = stringResource(id = R.string.flights_from, flights[0].departureCode),
                fontWeight = FontWeight.Bold,
                modifier = Modifier.padding(vertical = dimensionResource(id = R.dimen.padding_small))
            )
            LazyColumn {
                items(flights) { flight ->
                    Card(
                        modifier = Modifier
                            .fillMaxWidth()
                            .padding(
                                vertical = dimensionResource(id = R.dimen.padding_small)
                            )
                    ) {
                        Box(
                            modifier = Modifier
                                .fillMaxWidth()
                                .padding(dimensionResource(id = R.dimen.padding_medium))
                        ) {
                            Column(
                                verticalArrangement = Arrangement.spacedBy(dimensionResource(id = R.dimen.padding_mini_small))
                            ) {
                                Text(
                                    text = stringResource(id = R.string.depart),
                                    style = MaterialTheme.typography.titleMedium,
                                )
                                Row {
                                    Text(
                                        text = flight.departureCode,
                                        fontWeight = FontWeight.Bold,
                                        modifier = Modifier.padding(end = dimensionResource(id = R.dimen.padding_small))
                                    )
                                    Text(text = flight.departureName)
                                }
                                Spacer(modifier = Modifier.padding(vertical = dimensionResource(id = R.dimen.padding_mini_small)))
                                Text(
                                    text = stringResource(id = R.string.arrive),
                                    style = MaterialTheme.typography.titleMedium
                                )
                                Row {
                                    Text(
                                        text = flight.destinationCode,
                                        fontWeight = FontWeight.Bold,
                                        modifier = Modifier.padding(end = dimensionResource(id = R.dimen.padding_small))
                                    )
                                    Text(text = flight.destinationName)
                                }
                            }
                            Box(modifier = Modifier.align(Alignment.CenterEnd)) {
                                Icon(
                                    imageVector = Icons.Outlined.Star,
                                    tint = if (flight.isFavorite) Color(0xFFDDAC1D) else Color.Gray,
                                    contentDescription = null,
                                    modifier = Modifier.clickable {
                                        toggleFavorite(flight)
                                    }
                                )
                            }
                        }
                    }
                }
            }
        }
    }
}

//@Preview
//@Composable
//fun FlightSearchAppPreview() {
//    FlightSearchApp()
//}

@Preview(showBackground = true)
@Composable
fun FlightListPreview() {
    FlightList(
        flights = listOf(
            Flight(
                departureCode = "AAA",
                departureName = "ssss sss ssss",
                destinationCode = "BBB",
                destinationName = "bbbb bbbb bbb"
            )
        ),
        toggleFavorite = {}
    )
}